home *** CD-ROM | disk | FTP | other *** search
/ EnigmA Amiga Run 1997 July / EnigmA AMIGA RUN 20 (1997)(G.R. Edizioni)(IT)[!][issue 1997-07 & 08][EAR-CD IV].iso / earcd / dev / c / asyncio.lha / AsyncIO / src / WaitPacket.c < prev    next >
C/C++ Source or Header  |  1997-02-18  |  3KB  |  79 lines

  1. #include "async.h"
  2.  
  3.  
  4. /* this function waits for a packet to come back from the file system. If no
  5.  * packet is pending, state from the previous packet is returned. This ensures
  6.  * that once an error occurs, it state is maintained for the rest of the life
  7.  * of the file handle.
  8.  *
  9.  * MH: The above causes one minor problem though. SeekAsync() past EOF
  10.  * (can?) cause the file to be stuck in an error state, while DOS would
  11.  * allow file operations to continue anyway, based on the EOF position.
  12.  * This is mostly a compatibility problem though, and we've never said
  13.  * SeekAsync() was behaving just like Seek(). :) Fixing this isn't trivial,
  14.  * since it is hard to tell (AFAIK) if we really are at EOF, or a Seek() or
  15.  * a read failed due to other problems.
  16.  *
  17.  * This function also deals with IO errors, bringing up the needed DOS
  18.  * requesters to let the user retry an operation or cancel it.
  19.  */
  20. LONG
  21. AS_WaitPacket( AsyncFile *file )
  22. {
  23. #ifdef ASIO_NOEXTERNALS
  24.     struct ExecBase        *SysBase = file->af_SysBase;
  25.     struct DosLibrary    *DOSBase = file->af_DOSBase;
  26. #endif
  27.     LONG bytes;
  28.  
  29.     if( file->af_PacketPending )
  30.     {
  31.         while( TRUE )
  32.         {
  33.             /* This enables signalling when a packet comes back to the port */
  34.             file->af_PacketPort.mp_Flags = PA_SIGNAL;
  35.  
  36.             /* Wait for the packet to come back, and remove it from the message
  37.              * list. Since we know no other packets can come in to the port, we can
  38.              * safely use Remove() instead of GetMsg(). If other packets could come in,
  39.              * we would have to use GetMsg(), which correctly arbitrates access in such
  40.              * a case
  41.              */
  42.             Remove( ( struct Node * ) WaitPort( &file->af_PacketPort ) );
  43.  
  44.             /* set the port type back to PA_IGNORE so we won't be bothered with
  45.              * spurious signals
  46.              */
  47.             file->af_PacketPort.mp_Flags = PA_IGNORE;
  48.  
  49.             /* mark packet as no longer pending since we removed it */
  50.             file->af_PacketPending = FALSE;
  51.  
  52.             bytes = file->af_Packet.sp_Pkt.dp_Res1;
  53.  
  54.             if( bytes >= 0 )
  55.             {
  56.                 /* packet didn't report an error, so bye... */
  57.                 return( bytes );
  58.             }
  59.  
  60.             /* see if the user wants to try again... */
  61.             if( ErrorReport( file->af_Packet.sp_Pkt.dp_Res2, REPORT_STREAM, file->af_File, NULL ) )
  62.             {
  63.                 return( -1 );
  64.             }
  65.  
  66.             /* user wants to try again, resend the packet */
  67.             AS_SendPacket( file,
  68.                 file->af_Buffers[ file->af_ReadMode ?
  69.                     file->af_CurrentBuf :
  70.                     1 - file->af_CurrentBuf ] );
  71.         }
  72.     }
  73.  
  74.     /* last packet's error code, or 0 if packet was never sent */
  75.     SetIoErr( file->af_Packet.sp_Pkt.dp_Res2 );
  76.  
  77.     return( file->af_Packet.sp_Pkt.dp_Res1 );
  78. }
  79.